<template>
  <a-card :body-style="{ height: 'calc(100vh - 125px)' }">
    <a-row class="w-full flex justify-between mb-2">
      <a-space>
        <a-button @click="goBack">
          <template #icon>
            <icon-arrow-left />
          </template>
          <template #default>返回</template>
        </a-button>
      </a-space>
      <a-space>
        <a-button type="primary" @click="okBtnClick()">
          <template #icon>
            <icon-check />
          </template>
          <template #default>保存</template>
        </a-button>
      </a-space>
    </a-row>

    <a-spin
      :loading="spinLoading"
      :size="35"
      class="w-[100%]"
      tip="正在处理, 请稍候..."
    >
      <a-form ref="formRef" :model="form" :rules="rules" auto-label-width>
        <div class="flex justify-between" style="flex-wrap: wrap">
          <a-form-item
            class="w-[100%]"
            field="newsTitle"
            label="新闻标题"
            required
          >
            <a-input v-model="form.newsTitle" placeholder="新闻标题" />
          </a-form-item>
          <a-form-item
            class="w-[33%]"
            field="publishAuthorId"
            label="发布人"
            required
          >
            <a-select
              v-model="form.publishAuthorId"
              allow-clear
              allow-search
              placeholder="发布人"
            >
              <a-option
                v-for="(d, index) in dicts[proxy.DICT.userList]"
                :key="index"
                :label="d.dictValue"
                :value="String(d.dictKey)"
              />
            </a-select>
          </a-form-item>
          <a-form-item
            class="w-[33%]"
            field="publishDeptId"
            label="发布部门"
            tooltip="表示发布此新闻的部门，可为空"
          >
            <a-tree-select
              v-model="form.publishDeptId"
              :data="deptTree"
              :fieldNames="{
                key: 'deptId',
                title: 'deptName',
                children: 'children',
              }"
              allow-clear
              placeholder="发布部门"
            />
          </a-form-item>
          <a-form-item
            class="w-[33%]"
            field="newsTop"
            label="是否置顶"
            tooltip="置顶会让此新闻展示在最前面"
          >
            <a-radio-group v-model="form.newsTop" type="button">
              <a-radio
                v-for="(item, index) in dicts[proxy.DICT.yesNo]"
                :key="index"
                :value="item.dictKey"
                >{{ item.dictValue }}
              </a-radio>
            </a-radio-group>
          </a-form-item>
          <a-form-item
            class="w-[33%]"
            field="newsSort"
            label="排序值"
            tooltip="新闻的展示顺序，数值越小排序越靠前"
          >
            <a-input-number
              v-model="form.newsSort"
              :min="0"
              placeholder="排序值"
            />
          </a-form-item>
          <a-form-item
            class="w-[33%]"
            field="publishTime"
            label="发布时间"
            required
            tooltip="设置新闻的发布时间，不选择将立即发布"
          >
            <a-date-picker
              v-model="form.publishTime"
              class="w-[100%]"
              disabled-input
              format="YYYY-MM-DD HH:mm:ss"
              placeholder="发布时间"
              show-time
            />
          </a-form-item>
          <a-form-item class="w-[33%]" field="status" label="新闻状态" required>
            <a-select v-model="form.status" allow-clear placeholder="新闻状态">
              <a-option
                v-for="(d, index) in dicts[proxy.DICT.commonNumberStatus]"
                :key="index"
                :label="d.dictValue"
                :value="d.dictKey"
              />
            </a-select>
          </a-form-item>
          <a-form-item
            class="w-[100%]"
            field="newsPicFileId"
            label="新闻封面图"
          >
            <upload-file
              ref="uploadRef"
              :accept="fileAccept.img"
              :file-list="newsPicList"
              :file-source="fileSource.lindi_news_cover_img.key"
              :limit="1"
              :list-type="fileListType.pictureCard"
              :multiple="false"
            />
          </a-form-item>
          <a-form-item
            class="w-[100%]"
            field="newsContent"
            label="新闻内容"
            required
          >
            <tinymce-editor
              ref="editorRef"
              :editorHeight="450"
              :file-source="fileSource.lindi_news_content_img.key"
            />
          </a-form-item>
        </div>
      </a-form>
    </a-spin>
  </a-card>
</template>

<script setup>
import {
  getCurrentInstance,
  reactive,
  ref,
  watch,
  onMounted,
  onBeforeUnmount,
} from "vue";
import { useRoute, useRouter } from "vue-router";
import {
  addNewsApi,
  getNewsByNewsIdApi,
  updateNewsByNewsIdApi,
} from "~/api/lindi/news.js";
import { getDeptListApi } from "~/api/basic/dept.js";
import TinymceEditor from "~/components/tinymceEditor/index.vue";
import UploadFile from "~/components/uploadFile/index.vue";
import { fileAccept, fileListType, fileSource } from "~/utils/sys.js";

// 全局实例
const { proxy } = getCurrentInstance();
// 路由实例
const router = useRouter();
const route = useRoute();

// 加载字典
const dicts = proxy.LoadDicts([
  proxy.DICT.commonNumberStatus,
  proxy.DICT.yesNo,
  proxy.DICT.userList,
]);

// 加载中...
const spinLoading = ref(false);
// 表单ref
const formRef = ref(null);
// 表单
const form = reactive({
  // 新闻ID
  newsId: null,
  // 新闻标题
  newsTitle: null,
  // 新闻内容
  newsContent: null,
  // 新闻封面图
  newsPicFileId: null,
  // 是否置顶 -> 默认否
  newsTop: proxy.yesNo.no.key,
  // 排序值
  newsSort: null,
  // 发布部门
  publishDeptId: null,
  // 发布人
  publishAuthorId: null,
  // 发布时间
  publishTime: null,
  // 新闻状态
  status: null,
});

// 表单校验规则
const rules = {
  newsTitle: [
    { required: true, message: "新闻标题不能为空", trigger: "submit" },
  ],
  newsContent: [
    { required: true, message: "新闻内容不能为空", trigger: "submit" },
  ],
  publishAuthorId: [
    { required: true, message: "发布人不能为空", trigger: "submit" },
  ],
  publishTime: [
    { required: true, message: "发布时间不能为空", trigger: "submit" },
  ],
  status: [{ required: true, message: "新闻状态不能为空", trigger: "submit" }],
};

// 编辑器ref
const editorRef = ref(null);
// 上传组件ref
const uploadRef = ref(null);

// 封面图列表
const newsPicList = ref([]);

// 操作类型
const operationType = ref("");

// 检查表单是否有变更
const hasFormChanged = ref(false);

// 返回列表页
const goBack = () => {
  if (hasFormChanged.value) {
    proxy.$modal.confirm({
      title: "确认离开",
      content: "您有未保存的更改，确定要离开吗？",
      onOk: () => {
        router.push("/lindi/news/mgt");
      },
    });
  } else {
    router.push("/lindi/news/mgt");
  }
};

// 确定 -> 点击
const okBtnClick = () => {
  // 检查编辑器是否存在
  if (!editorRef.value) {
    proxy.$msg.error("编辑器未初始化完成，请稍后重试");
    return;
  }

  // 获取封面图片数据
  if (uploadRef.value) {
    form.newsPicFileId = uploadRef.value.getUploadFileId();
  }

  // 获取富文本数据
  form.newsContent = editorRef.value.getEditorContent();

  // 验证富文本内容
  if (
    !form.newsContent ||
    form.newsContent.trim() === "" ||
    form.newsContent === "<p></p>"
  ) {
    proxy.$msg.error("新闻内容不能为空");
    return;
  }

  // 表单验证
  formRef.value.validate((valid) => {
    if (valid) {
      return false;
    }

    // 添加
    if (operationType.value === proxy.operationType.add.type) {
      spinLoading.value = true;
      addNewsApi(form)
        .then((res) => {
          proxy.$msg.success(proxy.operationType.add.success);
          hasFormChanged.value = false; // 重置表单变更状态
          goBack();
        })
        .catch((error) => {
          console.error("添加新闻失败:", error);
          const errorMsg =
            error?.response?.data?.message ||
            error?.message ||
            "添加新闻失败，请重试";
          proxy.$msg.error(errorMsg);
        })
        .finally(() => {
          spinLoading.value = false;
        });
    }
    // 修改
    else if (operationType.value === proxy.operationType.update.type) {
      spinLoading.value = true;
      updateNewsByNewsIdApi(form)
        .then((res) => {
          proxy.$msg.success(proxy.operationType.update.success);
          hasFormChanged.value = false; // 重置表单变更状态
          goBack();
        })
        .catch((error) => {
          console.error("更新新闻失败:", error);
          const errorMsg =
            error?.response?.data?.message ||
            error?.message ||
            "更新新闻失败，请重试";
          proxy.$msg.error(errorMsg);
        })
        .finally(() => {
          spinLoading.value = false;
        });
    } else {
      proxy.$msg.error("操作类型未定义");
    }
  });
};

// 加载新闻详细信息
const loadNewsInfo = (newsId) => {
  if (!newsId) {
    proxy.$msg.error("新闻ID不能为空");
    return;
  }

  spinLoading.value = true;
  getNewsByNewsIdApi(newsId)
    .then((res) => {
      console.log(res);
      // 数据赋值
      if (res) {
        for (let key in res) {
          if (form.hasOwnProperty(key)) {
            form[key] = res[key];
          }
        }
        // 将newsSort转换为数字类型
        if (res.newsSort !== null && res.newsSort !== undefined) {
          form.newsSort = Number(res.newsSort);
        }
        // 富文本内容需要延迟设置，确保编辑器已初始化
        if (res.newsContent) {
          setTimeout(() => {
            if (editorRef.value) {
              editorRef.value.setEditorContent(res.newsContent);
            }
          }, 100);
        }
        // 处理封面图片显示
        if (res.newsPicFile) {
          // 设置表单中的封面图片ID
          form.newsPicFileId = res.newsPicFile.fileId;
          // 设置上传组件的文件列表用于显示
          newsPicList.value = [
            {
              url: res.newsPicFile.fileUrl,
              response: {
                fileId: res.newsPicFile.fileId,
                fileName: res.newsPicFile.fileName,
                fileUrl: res.newsPicFile.fileUrl,
              },
            },
          ];
          console.log("newsPicList", newsPicList.value);
        } else {
          form.newsPicFileId = null;
          newsPicList.value = [];
        }
        // 重置表单变更状态
        hasFormChanged.value = false;
      } else {
        proxy.$msg.error("新闻数据为空");
      }
    })
    .catch((error) => {
      console.error("加载新闻详情失败:", error);
      const errorMsg =
        error?.response?.data?.message ||
        error?.message ||
        "加载新闻详情失败，请重试";
      proxy.$msg.error(errorMsg);
    })
    .finally(() => {
      spinLoading.value = false;
    });
};

// 部门树数据
const deptTree = ref([]);

// 获取部门数据列表
const getDeptTree = () => {
  return getDeptListApi({})
    .then((res) => {
      deptTree.value = res || [];
      return res;
    })
    .catch((error) => {
      console.error("加载部门列表失败:", error);
      proxy.$msg.error("加载部门列表失败");
      deptTree.value = [];
      throw error;
    });
};

// 监听表单变更
watch(
  () => form,
  () => {
    hasFormChanged.value = true;
  },
  { deep: true }
);

// 监听路由参数变化
watch(
  () => route.query,
  (newQuery, oldQuery) => {
    // 重置表单变更状态
    hasFormChanged.value = false;

    // 获取新的路由参数
    const { type, newsId } = newQuery;
    operationType.value = type || proxy.operationType.add.type;

    // 重置表单数据
    Object.keys(form).forEach((key) => {
      if (key === "newsTop") {
        form[key] = proxy.yesNo.no.key;
      } else {
        form[key] = null;
      }
    });

    // 清空编辑器内容
    if (editorRef.value) {
      editorRef.value.setEditorContent("");
    }

    // 加载部门树和新闻信息
    getDeptTree()
      .then(() => {
        // 如果是编辑模式且有新闻ID，加载新闻信息
        if (operationType.value === proxy.operationType.update.type && newsId) {
          form.newsId = newsId;
          loadNewsInfo(newsId);
        }
      })
      .catch((error) => {
        console.error("路由参数变化处理失败:", error);
      });
  },
  { immediate: false, deep: true }
);

// 页面离开前确认
const beforeUnloadHandler = (event) => {
  if (hasFormChanged.value) {
    event.preventDefault();
    event.returnValue = "您有未保存的更改，确定要离开吗？";
    return "您有未保存的更改，确定要离开吗？";
  }
};

// 初始化页面数据
const initPageData = () => {
  // 获取路由参数
  const { type, newsId } = route.query;
  operationType.value = type || proxy.operationType.add.type;

  // 加载部门树
  getDeptTree()
    .then(() => {
      // 如果是编辑模式且有新闻ID，加载新闻信息
      if (operationType.value === proxy.operationType.update.type && newsId) {
        form.newsId = newsId;
        loadNewsInfo(newsId);
      }
    })
    .catch((error) => {
      console.error("页面初始化失败:", error);
    });
};

// 初始化页面数据
onMounted(() => {
  // 添加页面离开前确认
  window.addEventListener("beforeunload", beforeUnloadHandler);

  // 初始化页面数据
  initPageData();
});

// 组件卸载时清理
onBeforeUnmount(() => {
  window.removeEventListener("beforeunload", beforeUnloadHandler);
});
</script>
<style scoped></style>
